#ifndef NETWORKHANDLER_H
#define NETWORKHANDLER_H

#include <SDL_net.h>
#include <vector>
#include <map>
#include <pthread.h>
#include "NetworkTarget.h"

#define BUFFERSIZE 1024
#define MAXCOMS 8
#define TIMEOUT 3000

struct NetworkInputInfo;

typedef struct NetworkInputInfo NetworkInputInfo;

class NetworkHandler
{
public:
	NetworkHandler();
	~NetworkHandler();
	void addBroadcastMessage(char *message, int length, int recipient); //add something to send to all other players
	void broadcastMessages(); //tell the sender to flush the buffer
	void checkIncoming(int streamToWatch); //used by inputThread to watch the incomming data
	void checkOutgoing(); //used by outputThread to send outgoing data
	//add and remove targets
	void addTarget(int id, NetworkTarget *target);
	void removeTarget(int id);
protected:
	//methods used to look at the network
	void checkOutputToNetwork();
	//void getFromNetwork();
	void readSingleFrame(int connectionID);
	//add input watchers
	void addInputHandler(int streamToRead);
	//the data to write to the network
	char buffer[BUFFERSIZE];
	//who to tell about network messages
	std::map<int,NetworkTarget*> toUpdate;
	//the connections to watch
	TCPsocket connections[MAXCOMS];
	int numConnections;
	//used to see if any connections have data to read
	SDLNet_SocketSet socketState;
	//some threads for watching networks
	pthread_t inputThread[MAXCOMS];
	pthread_t outputThread;
	//are the threads live
	bool live;
	bool sendAll;
	//what is the next free position in the buffer
	int bufferPos;
	//is the buffer in use?
	pthread_mutex_t bufferLock;
	//is sendAll being modified?
	pthread_mutex_t sendAllLock;
	//are connections being added
	pthread_mutex_t connectionLock;
	//are targets being added
	pthread_mutex_t targetLock;
	//is the buffer ready for more data
	pthread_cond_t isBufferEmpty;
};

struct NetworkInputInfo{
	NetworkHandler *handler;
	int streamToWatch;
};

#endif
